package com.echovin.esb.gateway.locator;

import com.echovin.esb.gateway.model.GatewayErrorResponse;
import com.echovin.esb.gateway.service.GatewayErrorResponseService;
import lombok.extern.slf4j.Slf4j;
import org.apache.commons.lang3.StringUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Component;

import java.util.ArrayList;
import java.util.Iterator;
import java.util.List;
import java.util.Map;
import java.util.concurrent.ConcurrentHashMap;

@Slf4j
@Component
public class GatewayErrorResponseLocator {
    private Map<String, List<GatewayErrorResponse>> resourceMap = new ConcurrentHashMap<>();
    private Map<String, GatewayErrorResponse> defaultResourceMap = new ConcurrentHashMap<>();

    @Autowired
    GatewayErrorResponseService gatewayErrorResponseService;
    @Autowired
    GatewayServiceResourceLocator gatewayServiceResourceLocator;
    @Autowired
    GatewayServiceActionResourceLocator gatewayServiceActionResourceLocator;

    public GatewayErrorResponseLocator() {
    }

    /**
     * 清空缓存并刷新
     */
    public void refresh() {
        this.resourceMap.clear();
        this.resourceMap.putAll(this.loadResourceDefine());
        this.defaultResourceMap.clear();
        this.defaultResourceMap.putAll(this.loadDefaultResourceDefine());
    }

    /**
     * 根据请求路径和错误码获取对应错误码的返回格式，没有则获取默认全局错误码返回格式，都没有返回null
     * path->errorResponse
     * @param requestPath
     * @param errCode
     * @return
     */
    public String getErrorResponse(String requestPath, String errCode) {
        if (StringUtils.isEmpty(requestPath)) {
            return null;
        }

        String serviceId = gatewayServiceResourceLocator.getServiceId(requestPath);
        if (StringUtils.isEmpty(serviceId)) {
            return null;
        }

        String actionId = gatewayServiceActionResourceLocator.getServiceActionId(serviceId);
        if (StringUtils.isEmpty(actionId)) {
            return null;
        }

        // 先获取对应code的返回格式
        List<GatewayErrorResponse> resourceList = this.resourceMap.get(actionId);
        if (resourceList != null) {
            Iterator var3 = resourceList.iterator();
            while(var3.hasNext()) {
                GatewayErrorResponse gatewayErrorResponse = (GatewayErrorResponse) var3.next();
                if (!StringUtils.isEmpty(gatewayErrorResponse.getErrorCode()) && gatewayErrorResponse.getErrorCode().contentEquals(errCode)) {
                    return gatewayErrorResponse.getErrorResponse();
                }
            }
        }

        // 再获取全局默认值
        GatewayErrorResponse gatewayErrorResponse = this.defaultResourceMap.get(serviceId);
        if (gatewayErrorResponse != null) {
            return gatewayErrorResponse.getErrorResponse();
        }

        return null;
    }

    /**
     * 调用service查询所有的gateway默认异常返回格式，组装{[serviceId：GatewayErrorResponse]}
     */
    private Map<String, GatewayErrorResponse> loadDefaultResourceDefine() {
        Map<String, GatewayErrorResponse> map = new ConcurrentHashMap<>();
        try {
            List<GatewayErrorResponse> resourceList = gatewayErrorResponseService.getDefaultErrorResponse();
            if (resourceList == null) {
                return map;
            }

            Iterator var3 = resourceList.iterator();
            while(var3.hasNext()) {
                GatewayErrorResponse resource = (GatewayErrorResponse) var3.next();
                map.put(resource.getServiceId(), resource);
            }

        } catch (Exception e) {
            log.error("加载gateway默认异常返回格式错误:{}", e);
        }

        log.info("数据库加载默认异常返回格式{}", map.values());

        return map;
    }

    /**
     * 调用service查询所有的gateway非默认异常返回格式，组装{[actionId：{GatewayErrorResponse}]}
     */
    private Map<String, List<GatewayErrorResponse>> loadResourceDefine() {
        Map<String, List<GatewayErrorResponse>> map = new ConcurrentHashMap<>();
        try {
            List<GatewayErrorResponse> resourceList = gatewayErrorResponseService.getErrorResponse();
            if (resourceList == null) {
                return map;
            }

            Iterator var3 = resourceList.iterator();
            while(var3.hasNext()) {
                GatewayErrorResponse resource = (GatewayErrorResponse) var3.next();
                List<GatewayErrorResponse> atts = map.get(resource.getActionId());
                if (atts == null) {
                    atts = new ArrayList();
                }
                if (!atts.contains(resource)) {
                    atts.add(resource);
                }
                map.put(resource.getActionId(), atts);
            }

        } catch (Exception e) {
            log.error("加载gateway动作异常返回格式错误:{}", e);
        }

        log.info("数据库加载动作异常返回格式{}", map.values());

        return map;
    }
}
